package com.fausto.learnimprint.core.service.impl

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl
import com.fausto.learnimprint.cache.RedisCache
import com.fausto.learnimprint.cache.RedisKey
import com.fausto.learnimprint.core.mapper.TagMapper
import com.fausto.learnimprint.core.model.entity.Tag
import com.fausto.learnimprint.core.service.ITagService
import com.fausto.learnimprint.core.service.IUserService
import org.springframework.beans.factory.annotation.Autowired
import org.springframework.security.authentication.AuthenticationServiceException
import org.springframework.stereotype.Service

/**
 *
 *
 * 服务实现类
 *
 *
 * @author fausto
 * @since 2022-03-28
 */
@Service
class TagServiceImpl : ServiceImpl<TagMapper, Tag>(), ITagService {

    @Autowired
    lateinit var userService: IUserService

    @Autowired
    lateinit var tagMapper: TagMapper

    override fun save(tagName: String) {
        tagMapper.insert(Tag().apply {
            this.tagName = tagName
            this.userId = userService.findUserFromDatabase().userId
        })

    }

    @RedisCache(key = RedisKey.TAG_KEY)
    override fun findTagByUserId(): List<Tag> {
        val userId = userService.findUserFromDatabase().userId
        return tagMapper.selectList(
            QueryWrapper<Tag>().eq("user_id", userId)
        )
    }

    /**
     *  必须是该标签的拥有者或管理员才有资格修改
     */
    override fun updateTag(tagId: Int, tagName: String) {
        val valid = tagOperationValid(tagId)
        //数据库更新操作，符合条件方可调用
        if (valid){
            tagMapper.updateById(Tag().apply {
                this.tagId = tagId
                this.tagName = tagName
            })
        }else{
            throw AuthenticationServiceException("当前登录用户不具备更新标签操作的权限")
        }
    }

    /**
     *      删除标签的条件
     *          1. 登录用户是该标签的创建者或管理员
     *          2. 该标签未关联博文
     */
    override fun deleteTag(tagId: Int) {
        val valid = tagOperationValid(tagId)
        if (!valid){
            throw AuthenticationServiceException("当前登录用户不具备删除标签操作的权限")
        }
        val countBlogTag = tagMapper.countBlogTag(tagId)
        if (countBlogTag > 0){
            throw RuntimeException("该标签关联了博文，无法删除")
        }
        //验证通过，可以删除该标签
        tagMapper.deleteById(tagId)
    }

    /**
     *      验证登录用户是否对标签有操作权限
     */
    @RedisCache(key = RedisKey.TAG_KEY)
    private fun tagOperationValid(tagId: Int): Boolean{
        //获取创建该标签的用户ID
        val userId = tagMapper.selectById(tagId).userId
        //获取当前登陆用户的完整信息
        val user = userService.findUserFromDatabase()
        //当前登录用户是创建该标签的用户，有权限修改
        if (user.userId == userId) {
            return true
        }
        //判断登录用户是否为管理员
        //获取该登录用户的角色信息
        val roles = userService.getRoles(user)
        roles.forEach {
            //该用户是管理员具备权限
            if (it == "ADMIN") {
                return true
            }
        }
        //验证不通过
        return false
    }
}